import {textDecoder, textEncoder} from "./utils";

export default class InputStream {
    buffer: Int8Array
    view: DataView
    offset: number = 0

    constructor(  buffer: Int8Array) {
        this.buffer = buffer
        this.view = new DataView(this.buffer.buffer)
    }

    public readByte(): number {
        const value = this.view.getInt8(this.offset)
        this.offset += 1
        return value

    }

    public readShort(): number {
        const value = this.view.getInt16(this.offset)
        this.offset += 2
        return value
    }

    public readInt(): number {
        const value = this.view.getInt32(this.offset)
        this.offset += 4
        return value
    }

    public readLong(): number {
        const value = this.view.getBigInt64(this.offset)
        this.offset += 8
        return Number(value).valueOf()
    }

    public readFloat(): number {
        const value = this.view.getFloat32(this.offset)
        this.offset += 4
        return value
    }

    public readDouble(): number {
        const value = this.view.getFloat64(this.offset)
        this.offset += 8
        return value
    }

    public readString(): string {
        const length = this.readInt()

        const buffer = this.buffer.slice(this.offset, this.offset + length)
        const value = textDecoder.decode(buffer)
        this.offset += length
        return value
    }

    public readBytes(length: number): any {
        const buffer = this.buffer.buffer.slice(this.offset, this.offset + length)
        this.offset += length
        return buffer
    }



}

export class OutputStream{
    buffer: Int8Array
    view: DataView
    offset: number = 0

    constructor(length: number) {
        this.buffer = new Int8Array(length)
        this.view = new DataView(this.buffer.buffer)
    }



    public writeByte(value: number) {
        this.view.setInt8(this.offset, value)
        this.offset += 1
    }

    public writeShort(value: number) {
        this.view.setInt16(this.offset, value)
        this.offset += 2

    }

    public writeInt(value: number) {
        this.view.setInt32(this.offset, value)
        this.offset += 4

    }

    public writeLong(value: number) {
        this.view.setBigInt64(this.offset, BigInt(value))
        this.offset += 8

    }

    public writeFloat(value: number) {
        this.view.setFloat32(this.offset, value)
        this.offset += 4
    }

    public writeDouble(value: number) {
        this.view.setFloat64(this.offset, value)
        this.offset += 8
    }

    public writeString(value: string) {
        const buffer = textEncoder.encode(value)
        //uint8Array 转  Int8Array
        const buffer2 = new Int8Array(buffer.buffer)

        this.writeInt(buffer2.length)
        buffer2.forEach((value, index) => {

                this.view.setInt8(this.offset++, value)

            }
        )


    }
}